home *** CD-ROM | disk | FTP | other *** search
/ PCMania 81 / PCMania CD81_1.iso / PCMANIA / demosc81 / raytrac2.c < prev    next >
C/C++ Source or Header  |  1999-05-22  |  7KB  |  234 lines

  1. /*
  2.  HEY! PcManíacos:                                               
  3.  
  4.  Si queréis contactar con el autor de esta sección,             
  5.  ahora podéis hacerlo a través de su e-mail privado:            
  6.  
  7.  Miquel Barceló: (Demoscene)                                    
  8.                                e-mail: MBarceloJ@nexo.es        
  9.  
  10.  -------------------------------------------------------------- 
  11. */
  12.  
  13. #include <stdio.h>
  14. #include <math.h>
  15. #include <stdlib.h>
  16. #include <dos.h>
  17. #include <conio.h>
  18. #include <i86.h>
  19. #include <string.h>
  20. #include <math.h>
  21. #include "vesalint.h"
  22. #include "affine.c"
  23.   
  24. typedef struct RT_camera
  25. {
  26.     float xpos,ypos,zpos,d;
  27. }RT_CAMERA;
  28.  
  29. typedef struct RT_esfera 
  30. {
  31.     float  xpos,ypos,zpos,radi;
  32.     float  coeff;                               //coeficientes
  33.     VECTOR ambient,diffuse,specular;
  34.     float  brillo;
  35. }RT_ESFERA;
  36.  
  37. typedef struct RT_luz
  38. {
  39.     float xpos,ypos,zpos;
  40.     VECTOR color;
  41. }RT_LUZ;
  42.  
  43. typedef struct RT_escena
  44. {
  45.     int num_luz,num_esfera,num_camera;
  46.     RT_ESFERA *esferas;
  47.     RT_LUZ    *luces;
  48.     RT_CAMERA *cameras;
  49.  
  50.     VECTOR    ambient;
  51. }RT_ESCENA;     
  52.  
  53. #pragma aux Set_Mode=\
  54. "int    10h"\
  55. modify  [ax]\
  56. parm    [ax]
  57.  
  58. void RT_render(RT_ESCENA *esc, unsigned char *dest)             //primary render
  59. {
  60.     int    xc,yc,sc,lc,min_esfera,ppos;
  61.     float  bpart,disc,t1,t2,min_t,cos_angulo,brillo;
  62.     VECTOR ray,posicion,normal,v_luz,color;
  63.  
  64.     ppos=0;
  65.  
  66.     for (sc=0;sc<esc->num_esfera;sc++)
  67.         esc->esferas[sc].coeff=pow(esc->cameras->xpos-esc->esferas[sc].xpos,2)+
  68.                                pow(esc->cameras->ypos-esc->esferas[sc].ypos,2)+
  69.                                pow(esc->cameras->zpos-esc->esferas[sc].zpos,2)-
  70.                                pow(esc->esferas[sc].radi,2);
  71.  
  72.     for (yc=-100;yc<100;yc+=1)
  73.     for (xc=-160;xc<160;xc+=1)
  74.     {
  75.         min_t=1000000.0;
  76.         min_esfera=-1;
  77.         ray.v1=xc;
  78.         ray.v2=yc;
  79.         ray.v3=esc->cameras->d;
  80.         ray=unit_vtr(ray);
  81.         for (sc=0;sc<esc->num_esfera;sc++)
  82.         {
  83.             bpart=(esc->cameras->xpos-esc->esferas[sc].xpos)*ray.v1+
  84.                   (esc->cameras->ypos-esc->esferas[sc].ypos)*ray.v2+
  85.                   (esc->cameras->zpos-esc->esferas[sc].zpos)*ray.v3;
  86.             disc=pow(bpart,2)-esc->esferas[sc].coeff;
  87.             if (disc>0)
  88.             {
  89.                 disc=sqrt(disc);
  90.                 t1=-bpart+disc;
  91.                 t2=-bpart-disc;
  92.                 if ((t1>0)&&(t1<min_t))
  93.                 {
  94.                     min_t=t1;
  95.                     min_esfera=sc;
  96.                 }
  97.                 if ((t2>0)&&(t2<min_t))
  98.                 {
  99.                     min_t=t2;
  100.                     min_esfera=sc;
  101.                 }
  102.             }
  103.         }
  104.         if (min_esfera>=0)
  105.         {
  106.             posicion.v1=ray.v1*min_t;
  107.             posicion.v2=ray.v2*min_t;
  108.             posicion.v3=ray.v3*min_t;
  109.             normal.v1=(posicion.v1-esc->esferas[min_esfera].xpos)/esc->esferas[min_esfera].radi;
  110.             normal.v2=(posicion.v2-esc->esferas[min_esfera].ypos)/esc->esferas[min_esfera].radi;
  111.             normal.v3=(posicion.v3-esc->esferas[min_esfera].zpos)/esc->esferas[min_esfera].radi;
  112.             color.v1=esc->esferas[min_esfera].ambient.v1*esc->ambient.v1;
  113.             color.v2=esc->esferas[min_esfera].ambient.v2*esc->ambient.v2;
  114.             color.v3=esc->esferas[min_esfera].ambient.v3*esc->ambient.v3;
  115.             brillo=esc->esferas[min_esfera].brillo;
  116.             for (lc=0;lc<esc->num_luz;lc++)
  117.             {
  118.                 v_luz.v1=esc->luces[lc].xpos;
  119.                 v_luz.v2=esc->luces[lc].ypos;
  120.                 v_luz.v3=esc->luces[lc].zpos;
  121.                 v_luz=vtr_sub_vtr(v_luz,posicion);
  122.                 v_luz=unit_vtr(v_luz);
  123.                 cos_angulo=vtr_dot_mul_vtr(v_luz,normal);
  124.                 if (cos_angulo>0)
  125.                 {
  126.                     color.v1+=cos_angulo*esc->esferas[min_esfera].diffuse.v1*esc->luces[lc].color.v1;
  127.                     color.v2+=cos_angulo*esc->esferas[min_esfera].diffuse.v2*esc->luces[lc].color.v2;
  128.                     color.v2+=cos_angulo*esc->esferas[min_esfera].diffuse.v3*esc->luces[lc].color.v3;
  129.                 }
  130.             }
  131.             dest[ppos  ]=max(min(color.v3,254),0);
  132.             dest[ppos+1]=max(min(color.v2,254),0);
  133.             dest[ppos+2]=max(min(color.v1,254),0);
  134.         }
  135.         else
  136.         {
  137.             dest[ppos  ]=0;
  138.             dest[ppos+1]=0;
  139.             dest[ppos+2]=0;
  140.         }
  141.         ppos+=3;
  142.     }
  143. }
  144.  
  145. RT_ESCENA *ray_testing;
  146. unsigned char *Virtpant1;
  147. void main(int argc, char *argv[])
  148. {
  149.     float movi=0;
  150.  
  151.     ray_testing=malloc(sizeof(RT_ESCENA));
  152.     ray_testing->num_esfera =1;
  153.     ray_testing->num_camera =1;
  154.     ray_testing->num_luz    =1;
  155.     ray_testing->esferas=malloc(sizeof (RT_ESFERA)*ray_testing->num_esfera);
  156.     ray_testing->cameras=malloc(sizeof (RT_CAMERA)*ray_testing->num_camera);
  157.     ray_testing->luces  =malloc(sizeof (RT_LUZ   )*ray_testing->num_luz);
  158.  
  159.     ray_testing->ambient.v1=128;
  160.     ray_testing->ambient.v2=128;
  161.     ray_testing->ambient.v3=128;
  162.  
  163.     ray_testing->esferas[0].xpos=0;
  164.     ray_testing->esferas[0].ypos=0;
  165.     ray_testing->esferas[0].zpos=900;
  166.     ray_testing->esferas[0].radi=150;
  167.     ray_testing->esferas[0].ambient.v1=0.5;
  168.     ray_testing->esferas[0].ambient.v2=0;
  169.     ray_testing->esferas[0].ambient.v3=0;
  170.     ray_testing->esferas[0].diffuse.v1=0.5;
  171.     ray_testing->esferas[0].diffuse.v2=0.25;
  172.     ray_testing->esferas[0].diffuse.v3=0;
  173.     ray_testing->esferas[0].specular.v1=0.0;
  174.     ray_testing->esferas[0].specular.v2=0.0;
  175.     ray_testing->esferas[0].specular.v3=0.0;
  176.     ray_testing->esferas[0].brillo=5;
  177.     
  178.     ray_testing->luces[0].xpos=-100;
  179.     ray_testing->luces[0].ypos=-100;
  180.     ray_testing->luces[0].zpos=600;
  181.     ray_testing->luces[0].color.v1=255;
  182.     ray_testing->luces[0].color.v2=255;
  183.     ray_testing->luces[0].color.v3=255;
  184.  
  185.     ray_testing->cameras[0].xpos=0;   
  186.     ray_testing->cameras[0].ypos=0;   
  187.     ray_testing->cameras[0].zpos=0;
  188.     ray_testing->cameras[0].d=256;
  189.  
  190.     Virtpant1=malloc(320*200*3);
  191.     Active.Screen.Width=320;
  192.     Active.Screen.Height=200;
  193.     Active.Screen.bpp=32;
  194.  
  195.     Active.Work.Width=320;
  196.     Active.Work.Height=200;
  197.     Active.Work.bpp=24;
  198.  
  199.     Active.EnableLFB=1;
  200.  
  201.     if (!InitSetMode())
  202.     {
  203.         Active.Screen.bpp=24;
  204.         if (!InitSetMode())
  205.         {
  206.             Active.Screen.bpp=16;
  207.             if (!InitSetMode())
  208.             {
  209.                 Active.Screen.bpp=15;
  210.                 if (!InitSetMode())
  211.                 {
  212.                     Active.Screen.bpp=-1;
  213.                     Active.Screen.Height*=2;
  214.                     InitSetMode();
  215.                 }
  216.             }
  217.         }
  218.     }
  219.                 
  220.     while (!kbhit())
  221.     {
  222.         ray_testing->luces[0].xpos=500*sin(movi/10);
  223.         ray_testing->luces[0].zpos=1000-500*cos(movi/10);
  224.         movi++;
  225.         RT_render(ray_testing,Virtpant1);
  226.         Flip(Virtpant1);
  227.     }
  228.     getch();
  229.     Free_Memory();
  230.     Set_Mode(0x3);
  231. }
  232.  
  233.  
  234.